#!/usr/bin/env python3

from tkinter import Tk, Label, Canvas, PhotoImage, font, Text
from PIL import ImageTk, Image
import serial, time, io, sys

ser = serial.Serial (
    port = '/dev/ttyUSB1',
    baudrate = 115200,
    parity = serial.PARITY_NONE,
    stopbits = serial.STOPBITS_ONE,
    bytesize = serial.EIGHTBITS
)

# It's 2021, and Python3 still relies on Tk/TCL
root = Tk()
root.title ("MOMO CONTROL")
root.columnconfigure(0, weight=1)
root.rowconfigure(0, weight=1)
canvas = Canvas (root, width=640, height=502, background='grey85')
canvas.grid (column=0, row=0)
nicefont = font.Font (family='Mona', weight="bold", size=12)
statusbar = 482
pic = Label (root)
myimg = ImageTk.PhotoImage (Image.open ('momo.jpg'))
pic['image'] = myimg
pic.place (x = 0, y = 0)

keystate = 0
cmd = 0
opt = 0
imageuploading = 0
running = True

def key_pressed (event):
    global keystate, cmd, opt, imageuploading, running, ser

    c = event.char
    if imageuploading:
        return

    if c == 'q':
        running = False

    if (c >= 'a' and c <= 'z') or (c >= 'A' and c <= 'Z'):
        cmd = ord(c)
        w = Label (root, font=nicefont, text=event.char + "                                ")
        w.place (x = 0, y = statusbar)

    if c >= '0' and c <= '9':
        opt = ord(c)
        w = Label (root, font=nicefont, text=chr(cmd) + " " + event.char)
        w.place (x = 0, y = statusbar)
        keystate = 1

root.bind ("<Key>", key_pressed)

imagedata = []
lhb = -1

while running == True:
    sys.stdout.flush()
    root.update_idletasks()
    root.update()

    if keystate == 1:
        keystate = 0
        print ("cmd="+ chr(cmd), "opt=" + chr(opt) + "                                ")
        ser.write ([cmd, opt])
        ser.flush()

    if ser.in_waiting:
        line = ser.readline()
        #print (line)
        #sys.stdout.flush()
        if ((line[0] >= 65 and line[0] <= 90) or (line[0] >= 97 and line[0] <= 122)):
            w = Label (root, font=nicefont, text=str(line, 'UTF-8'))
            w.place (x = 32, y = statusbar)
            continue

        hb = line[1:2]
        if hb != lhb:
            w = Label (root, font=nicefont, text=hb+b"                                ")
            w.place (x = 0, y = statusbar)
            lhb = hb

        if int (line[1:5], 16) != 65535:
            imagedata.append(line)
        else:
            w = Label (root, font=nicefont, text="                                ")
            w.place (x = 0, y = statusbar)
            print ("last line received:", line)
            itsr =  int(line[5:7], 16)
            itschunk = int(line[7:9], 16)
            itsfilesize = int(line[9:13], 16)
            itspointer = int(line[13:17], 16)
            itschecksum = int(line[17:21], 16)
            itsreason = int(line[21:23], 16)
            print ("r=",itsr,"chunk=",itschunk,"filesize=",itsfilesize, "pointer=",\
                   itspointer,"checksum=",itschecksum,"reason=",itsreason)

            imageraw = bytearray (bytes([255])*65536)
            checksum = 0
            for thisline in imagedata:
                l = len(thisline) - 3
                addr = int (thisline[1:5], 16)
                for i in range (5, l, 2):
                    imageraw[addr] = int(thisline[i:i+2], 16)
                    checksum += imageraw[addr]
                    addr += 1

            print ("checksum=", checksum & 65535)
            l = 65535
            while imageraw[l] == 255:
                l = l - 1
            imageraw = imageraw[:l+1]

            try:
                image = Image.open (io.BytesIO (imageraw))
                image.verify()  # doesn't work very well!
            except:
                print ("Bad image download!")
                continue

            filename = time.strftime ("%Y%m%d-%H%M%S.jpg")
            print ("Creating", filename)
            newfile = open (filename, "wb")
            newfile.write (imageraw)
            newfile.close()
            try:
                newimg = ImageTk.PhotoImage (Image.open (filename))
                pic['image'] = newimg
            except:
                print ("...didn't work")
                pic['image'] = myimg
            imagedata = []

ser.close()
